package org.yohailong.mock.client.network;


import com.google.gson.Gson;
import io.reactivex.rxjava3.core.Observable;
import okhttp3.*;
import retrofit2.Retrofit;
import retrofit2.adapter.rxjava3.RxJava3CallAdapterFactory;
import retrofit2.converter.gson.GsonConverterFactory;

import java.util.HashMap;
import java.util.List;
import java.util.Objects;
import java.util.concurrent.TimeUnit;

public class RetrofitManager {

    private static final long CONNECT_TIMEOUT = 15;
    private static final long READ_TIMEOUT = 15;
    private static final long WRITE_TIMEOUT = 15;
    private OkHttpClient mOkHttpClient;
    private HashMap<String, Retrofit> mRetrofitMap = new HashMap<>();
    private Retrofit defaultRetrofit;

    private RetrofitManager(List<Interceptor> interceptors, String host) {
        OkHttpClient.Builder builder = new OkHttpClient.Builder()
                .connectTimeout(CONNECT_TIMEOUT, TimeUnit.SECONDS)
                .readTimeout(READ_TIMEOUT, TimeUnit.SECONDS)
                .writeTimeout(WRITE_TIMEOUT, TimeUnit.SECONDS);

        if (interceptors != null && !interceptors.isEmpty()) {
            for (Interceptor interceptor : interceptors) {
                builder.addInterceptor(interceptor);
            }
        }
        mOkHttpClient = builder.build();
        defaultRetrofit = new Retrofit.Builder()
                .baseUrl(host)
                .client(mOkHttpClient)
                .addConverterFactory(GsonConverterFactory.create(new Gson()))
                .addCallAdapterFactory(RxJava3CallAdapterFactory.create())
                .build();
        mRetrofitMap.put(host, defaultRetrofit);
    }


    private static RetrofitManager retrofitManager;

    public static void init(List<Interceptor> interceptors, String host) {
        retrofitManager = new RetrofitManager(interceptors, host);
    }


    public static RetrofitManager getInstance() {
        if (retrofitManager == null) {
            throw new RuntimeException("RetrofitManager must be init before user");
        }
        return retrofitManager;
    }


    /**
     * 创建Retrofit Api
     *
     * @param clazz Class<T>
     * @param host  String? 若host 为null则使用默认的retrofit
     * @return T
     */
    public <T> T createServerApi(Class<T> clazz, String host) {
        if (host == null) {
            return createServerApi(clazz);
        }
        if (host.isEmpty()) {
            throw new NullPointerException(" host can't be null or empty !");
        }
        Retrofit otherRetrofit;
        if (mRetrofitMap.containsKey(host)) {
            otherRetrofit = mRetrofitMap.get(host);
        } else {
            otherRetrofit = defaultRetrofit.newBuilder()
                    .baseUrl(host)
                    .build();
            mRetrofitMap.put(host, otherRetrofit);
        }
        return otherRetrofit.create(clazz);
    }

    public <T> T createServerApi(Class<T> clazz) {
        return defaultRetrofit.create(clazz);
    }


    public OkHttpClient getOkHttpClient() {
        return mOkHttpClient;
    }

    public Observable<String> requestSpecialHttp(Request request) {
        return Observable.just(request)
                .map(req -> {
                    Call call = mOkHttpClient.newCall(req);
                    Response execute = call.execute();
                    return Objects.requireNonNull(execute.body()).string();
                });
    }


}
